package com.gitee.linzl.zuul.gateway.config;

import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import java.util.Map;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.cloud.netflix.zuul.filters.Route;
import org.springframework.cloud.netflix.zuul.filters.RouteLocator;
import org.springframework.cloud.netflix.zuul.filters.ZuulProperties;
import org.springframework.cloud.netflix.zuul.filters.ZuulProperties.ZuulRoute;
import org.springframework.context.annotation.Primary;
import org.springframework.stereotype.Component;

import com.google.common.base.Optional;

import lombok.extern.slf4j.Slf4j;
import springfox.documentation.spring.web.plugins.Docket;
import springfox.documentation.swagger.web.SwaggerResource;
import springfox.documentation.swagger.web.SwaggerResourcesProvider;

/**
 * 参考 InMemorySwaggerResourcesProvider
 * 
 * 聚合所有微服务的swagger
 */
@Component
@Primary
@Slf4j
public class AggregateSwagger implements SwaggerResourcesProvider {
	@Autowired
	private RouteLocator routeLocator;// 会发现在eureka上等的client
	@Autowired
	private ZuulProperties properties;

	@Override
	public List<SwaggerResource> get() {
		log.debug("==========生成api==========");
		List<SwaggerResource> resources = new ArrayList<SwaggerResource>();

		List<Route> routes = routeLocator.getRoutes();
		routes.stream().forEach((route) -> {
			int lastIndex = route.getFullPath().lastIndexOf("/");
			String fullPath = route.getFullPath().substring(0, lastIndex);
			resources.add(resource(route.getId(), fullPath + "/v2/api-docs"));
		});

		Map<String, ZuulRoute> map = properties.getRoutes();
		map.forEach((key, zuulRoute) -> {
			int lastIndex = zuulRoute.getPath().lastIndexOf("/");
			String fullPath = zuulRoute.getPath().substring(0, lastIndex);
			resources.add(resource(zuulRoute.getServiceId(), fullPath + "/v2/api-docs"));
		});

		Collections.sort(resources);
		return resources;

	}

	private SwaggerResource resource(String swaggerGroup, String baseUrl) {
		SwaggerResource swaggerResource = new SwaggerResource();
		swaggerResource.setName(swaggerGroup);
		swaggerResource.setLocation(swaggerLocation(baseUrl, swaggerGroup));
		swaggerResource.setSwaggerVersion("2.0");
		return swaggerResource;
	}

	private String swaggerLocation(String swaggerUrl, String swaggerGroup) {
		String base = Optional.of(swaggerUrl).get();
		if (Docket.DEFAULT_GROUP_NAME.equals(swaggerGroup)) {
			return base;
		}
		return base + "?group=all";// + swaggerGroup;
	}
}
